package funcs

import (
	"errors"
	"fmt"
	"gitee.com/wanjimao/common-util/dancetiktok/enums/dancetiktokenums"
	dancetiktokenumsredis "gitee.com/wanjimao/common-util/dancetiktok/enums/dancetiktokenumsmyredis"
	"github.com/go-redis/redis"
	"hash/crc32"
	"strconv"
)

// UserIdHashMatchNodeTag 用户id一致性哈希匹配服务节点标识
func UserIdHashMatchNodeTag(env, userId string) string {
	nodeTags := dancetiktokenumsredis.ServiceNodeEnumsObject.EnvServiceNodeTags(env)
	// 计算哈希值
	hashValue := int(crc32.ChecksumIEEE([]byte(userId)))
	// 映射到节点
	index := hashValue % len(nodeTags)
	return nodeTags[index]
}

// GenerateFriendId 用户Id生成唯一纯8位递增数字
func GenerateFriendId(userId string, envServer string, platForm string, rdsClient *redis.ClusterClient) (string, error) {
	if userId == "" {
		fmt.Println(fmt.Sprintf("GenerateFriendId userId is empty"))
		return "", errors.New("userId is empty")
	}
	userIdFriendKey := fmt.Sprintf(dancetiktokenums.UserIdMatchFriendIdHash, envServer, platForm)
	friendIdUserKey := fmt.Sprintf(dancetiktokenums.FriendIdMatchUserIdHash, envServer, platForm)
	friendId, err := rdsClient.HGet(userIdFriendKey, userId).Result()
	if err != nil && redis.Nil != err {
		fmt.Println(fmt.Sprintf("GenerateFriendId 获取用户小id异常 userId[%+v] friendId[%+v] err[%+v]", userId, friendId, err))
		return friendId, err
	}
	if friendId != "" {
		return friendId, nil
	} else { // 用户需要生成小id
		incrKey := fmt.Sprintf(dancetiktokenums.FriendIdIncrNumberString, envServer, platForm)
		incrVal, err := rdsClient.Get(incrKey).Result()
		if err != nil && redis.Nil != err {
			fmt.Println(fmt.Sprintf("GenerateFriendId 获取最新递增小id异常 userId[%+v] incrKey[%+v] err[%+v]", userId, incrKey, err))
			return friendId, err
		}

		newFriendIdStr := "10000000"
		if incrVal == "" { // 第一累计数字,从 10000000 开始
			err = rdsClient.Set(incrKey, 10000000, 0).Err()
			if err != nil && redis.Nil != err {
				fmt.Println(fmt.Sprintf("GenerateFriendId 设置递增初始值异常 userId[%+v] incrKey[%+v] err[%+v]", userId, incrKey, err))
				return friendId, err
			}
		} else {
			newFriendId, err := rdsClient.Incr(incrKey).Result()
			newFriendIdStr = strconv.FormatInt(newFriendId, 10)
			if err != nil && redis.Nil != err {
				fmt.Println(fmt.Sprintf("GenerateFriendId 获取最新递增小id异常 userId[%+v] incrKey[%+v] newFriendId[%+v] err[%+v]", userId, incrKey, newFriendId, err))
				return newFriendIdStr, err
			}
		}

		// 更新用户id映射小id
		err = rdsClient.HSet(userIdFriendKey, userId, newFriendIdStr).Err()
		if err != nil && redis.Nil != err {
			fmt.Println(fmt.Sprintf("GenerateFriendId 更新用户id映射小id异常 userId[%+v] friendId[%+v] err[%+v]", userId, newFriendIdStr, err))
			return friendId, err
		}

		// 更新小id映射用户id
		err = rdsClient.HSet(friendIdUserKey, newFriendIdStr, userId).Err()
		if err != nil && redis.Nil != err {
			fmt.Println(fmt.Sprintf("GenerateFriendId 更新小id映射用户id异常 userId[%+v] friendId[%+v] err[%+v]", userId, newFriendIdStr, err))
			return friendId, err
		}
		return newFriendIdStr, nil
	}
}
